/*  ----------------------------------------------------------------------------
 *  Arello Mobile
 *  Fast 3d Engine
 *  ----------------------------------------------------------------------------
 * Except where otherwise noted, this work is licensed under
 * http://creativecommons.org/licenses/by/3.0
 */

#ifndef __TEXTSTREAM_H__
#define __TEXTSTREAM_H__

#include <Converter.h>

namespace liba
{
namespace textstream
{

/** This stream is far less effective, than std::stream. But it is far less
	complicated also. */
template<class Sym>
class TextOStream
{
public:
	virtual ~TextOStream()
	{}
	virtual void print(const Sym * begin, const Sym * end)=0;
	virtual void flush()=0;
};

/** This template function prints to stream the object of any type, that has 
	ConverterTraits. */
template<class Sym, class T>
inline TextOStream<Sym> & operator<<(TextOStream<Sym> & ts, const T & value)
{
	typename converter::ConverterTraits< Sym, T >::Buffer buf;
	if( buf.convert( value ) )
		ts.print( buf.begin(), buf.end() );
	return ts;
}

/** Microsoft Visual Studio 6 distincts char[n] type from char * type
	and that's why this specialization is reqired to print literals. */
template< class Sym >
inline TextOStream<Sym> & operator<<(TextOStream<Sym> & ts, const Sym * value)
{
	typename converter::ConverterTraits< Sym, const Sym * >::Buffer buf;
	if( buf.convert( value ) )
		ts.print( buf.begin(), buf.end() );
	return ts;
}

/** Microsoft Visual Studio 6 distincts char[n] type from char * type
	and that's why this specialization is reqired to print literals. */
template< class Sym >
inline TextOStream<Sym> & operator<<(TextOStream<Sym> & ts, Sym * value)
{
	typename converter::ConverterTraits< Sym, const Sym * >::Buffer buf;
	if( buf.convert( value ) )
		ts.print( buf.begin(), buf.end() );
	return ts;
}

} // namespace textstream
} // namespace liba

using namespace liba;

#endif //__TEXTSTREAM_H__